/*
 * Copyright (C) 2021 Huawei Device Co., Ltd.
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *
 */

package com.github.florent37.camerafragment.internal.manager.impl;

import com.github.florent37.camerafragment.configuration.Configuration;
import com.github.florent37.camerafragment.configuration.ConfigurationProvider;
import com.github.florent37.camerafragment.internal.manager.CameraManager;
import com.github.florent37.camerafragment.internal.utils.Size;

import ohos.app.Context;
import ohos.eventhandler.EventHandler;
import ohos.eventhandler.EventRunner;
import ohos.media.recorder.Recorder;
import ohos.media.recorder.RecorderProfile;

/**
 * 相机管理基类
 *
 * @param <Integer>
 * @param <SurfaceListener>
 * @since 2021-05-24
 */
abstract class BaseCameraManager<Integer, SurfaceListener>
    implements CameraManager<Integer, SurfaceListener>, Recorder.IRecorderListener {
    private static final String TAG = "BaseCameraManager";
    /**
     * 上下文
     */
    protected Context context;
    boolean isVideoRecording = false;
    java.lang.Integer mCurrentCameraId = null;
    java.lang.Integer faceFrontCameraId = null;
    java.lang.Integer faceBackCameraId = null;
    int numberOfCameras = 0;
    int faceFrontCameraOrientation;
    int faceBackCameraOrientation;
    Size photoSize;
    Size videoSize;
    Size previewSize;
    Size windowSize;
    Recorder videoRecorder;
    RecorderProfile camcorderProfile;
    ConfigurationProvider configurationProvider;
    EventRunner backgroundThread;
    EventHandler backgroundHandler;
    EventHandler uiHandler = new EventHandler(EventRunner.getMainEventRunner());

    @Override
    public void initializeCameraManager(ConfigurationProvider provider, Context context1) {
        this.context = context1;
        this.configurationProvider = provider;
        startBackgroundThread();
    }

    @Override
    public void releaseCameraManager() {
        this.context = null;
        stopBackgroundThread();
    }

    protected abstract void prepareCameraOutputs(String camera);

    protected abstract void onMaxDurationReached();

    protected abstract void onMaxFileSizeReached();

    protected abstract int getPhotoOrientation(@Configuration.SensorPosition int sensorPosition);

    protected abstract int getVideoOrientation(@Configuration.SensorPosition int sensorPosition);

    protected void releaseVideoRecorder() {
        if (videoRecorder != null) {
            videoRecorder.stop();
            videoRecorder.reset();
            videoRecorder.release();
            videoRecorder = null;
        }
    }

    private void startBackgroundThread() {
        backgroundThread = EventRunner.create(TAG);
        backgroundHandler = new EventHandler(backgroundThread);
    }

    private void stopBackgroundThread() {
        backgroundThread = null;
        backgroundHandler = null;
    }

    // 媒体注册异常回调
    public void onError(int what, int extra) {
        if (what == Recorder.RecorderOnInfoType.MEDIA_RECORDER_INFO_MAX_DURATION_REACHED) {
            onMaxDurationReached();
        } else if (what == Recorder.RecorderOnInfoType.MEDIA_RECORDER_INFO_MAX_FILESIZE_REACHED) {
            onMaxFileSizeReached();
        }
    }

    // 媒体注册正常或者打印
    @Override
    public void onMessage(int ii, int i1) {
    }

    public boolean isVideoRecording() {
        return isVideoRecording;
    }

    /**
     * 获取当前相机ID
     *
     * @return int相机ID
     */
    public int getCurrentCameraId() {
        return mCurrentCameraId == null ? faceBackCameraId : mCurrentCameraId;
    }

    /**
     * 获取前置相机ID
     *
     * @return int前置相机Id
     */
    public int getFaceFrontCameraId() {
        return faceFrontCameraId == null ? 1 : faceFrontCameraId;
    }

    /**
     * 获取后置相机ID
     *
     * @return int后置相机Id
     */
    public int getFaceBackCameraId() {
        return faceBackCameraId == null ? 0 : faceBackCameraId;
    }

    /**
     * 获取相机设备数量
     *
     * @return int 相机设备数量
     */
    public int getNumberOfCameras() {
        return numberOfCameras;
    }

    /**
     * 前置相机方向
     *
     * @return int前置方向
     */
    public int getFaceFrontCameraOrientation() {
        return faceFrontCameraOrientation;
    }

    /**
     * 获取后置相机方向
     *
     * @return int 后置方向
     */
    public int getFaceBackCameraOrientation() {
        return faceBackCameraOrientation;
    }

    /**
     * 设置相机ID
     *
     * @param currentCameraId 当前相机Id
     */
    public void setCameraId(java.lang.Integer currentCameraId) {
        this.mCurrentCameraId = currentCameraId;
    }
}
